"""
# 迭代器对象从集合的第一个元素开始访问，直到所有的元素被访问完结束。迭代器只能往前不会后退。
list=[1,2,3,4]
it = iter(list)    # 创建迭代器对象
print (next(it))   # 输出迭代器的下一个元素
print (next(it))

#!/usr/bin/python3
# 迭代器对象可以使用常规for语句进行遍历：
list=[1,2,3,4]
it = iter(list)    # 创建迭代器对象
for x in it:
    print (x, end=" ")
print('========================')
# 也可以使用 next() 函数：
from _typeshed import Self
import sys
list = [1,2,3,4,5]
it = iter(list)     # 创建迭代器对象
while True:
    try:
        print(next(it))
    except StopIteration:
        sys.exit()
"""

'''
创建一个迭代器
把一个类作为一个迭代器使用需要在类中实现两个方法 __iter__() 与 __next__() 。
__iter__() 方法返回一个特殊的迭代器对象， 这个迭代器对象实现了 __next__() 方法并通过 StopIteration 异常标识迭代的完成。
__next__() 方法（Python 2 里是 next()）会返回下一个迭代器对象。
创建一个返回数字的迭代器，初始值为 1，逐步递增 1：
'''
class MyNumbers:
    def __iter__(self):
        self.a=1
        return self
    def __next__(self):
        x=self.a
        self.a+=1
        return x
myclass = MyNumbers()
myiter = iter(myclass)
print(next(myiter))
print(next(myiter))
print(next(myiter))
print(next(myiter))
print(next(myiter))

# StopIteration
# StopIteration 异常用于标识迭代的完成，防止出现无限循环的情况，在 __next__() 方法中我们可以设置在完成指定循环次数后触发 StopIteration 异常来结束迭代。
class MyNumbers1():
    def __iter__(self):
        self.a=1
        return self
    def __next__(self):
        if self.a <=10: # 在 10 次迭代后停止执行：
            x=self.a
            self.a += 1
            return x
        else:
            raise StopIteration
myclass1=MyNumbers1()
myiter1 =iter(myclass1)
for x in myiter1:
    print(x)

# 生成器
# 使用了 yield 的函数被称为生成器（generator）。
# 调用一个生成器函数，返回的是一个迭代器对象。
# 以下实例使用 yield 实现斐波那契数列：
#!/usr/bin/python3
import sys
def fibonacci(n): # 生成器函数 - 斐波那契
    a, b, counter = 0, 1, 0
    while True:
        if (counter > n): 
            return
        yield a
        a, b = b, a + b
        counter += 1
f = fibonacci(10) # f 是一个迭代器，由生成器返回生成
while True:
    try:
        print (next(f), end=" ")
    except StopIteration:
        sys.exit()